﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using DAL;
using System.Web.Security;
using GrupyzServices.BdAccess;

namespace PreBuildGrupyz.Models
{
    public class ShoppingCart
    {
        GrupyzEntities gr = new GrupyzEntities();
        string shoppingCartId { get; set; }
        public const string CartSessionKey = "CartId";
        public int LastCartCount { get; set; }
        public int IDCliente { get; set; }
        private const int QtdMax = 5;

        public static ShoppingCart GetCart(HttpContextBase context)
        {
            var cart = new ShoppingCart();
            cart.shoppingCartId = cart.GetCartId(context);
            cart.IDCliente = HttpContext.Current.User.Identity.Name == "" ? BitConverter.ToInt32(Guid.NewGuid().ToByteArray(),0) : int.Parse(HttpContext.Current.User.Identity.Name);
            return cart;
        }

        public bool AddToCart(Deal deal,bool Oferta)
        {
            var QuerycartItem = from c in gr.Cart
                where (c.IdSession == shoppingCartId || c.ClienteId == IDCliente)
                select c;

            if (QuerycartItem != null)
            {
                foreach (var item in QuerycartItem)
                {
                    gr.Cart.DeleteObject(item);    
                }
                gr.SaveChanges();
            }
               Cart cartItem = new Cart
                {
                    DealId  = deal.Id,
                    IdSession = shoppingCartId,
                    Quantidade = 1,
                    ClienteId = IDCliente,
                    Oferta = Oferta
                };
                gr.Cart.AddObject(cartItem);
                gr.SaveChanges();
                return true;
        }


        public void AddToCart(int Id, int quantidade)
        {
            var cartItem = gr.Cart.SingleOrDefault(
                c => (c.IdSession == shoppingCartId || c.ClienteId == IDCliente));

            cartItem.Quantidade = quantidade;

            gr.SaveChanges();
        }

        public void AddPontosToCart(int Id, int pontos)
        {
            var cartItem = gr.Cart.SingleOrDefault(
                c => (c.IdSession == shoppingCartId || c.ClienteId == IDCliente));

            cartItem.Pontos = pontos;

            cartItem.Desconto = pontos;

            gr.SaveChanges();
        }

        public int GetValorDesconto()
        {
            return gr.Cart.SingleOrDefault(
                c => (c.IdSession == shoppingCartId || c.ClienteId == IDCliente)).Desconto;
        }

        public bool AddOfertas(OrderDetailViewModel orderDetail)
        {
            try
            {
                var cartItem = gr.Cart.SingleOrDefault(
                        c => (c.IdSession == shoppingCartId || c.ClienteId == IDCliente));

                DadosOferta res = new DadosOferta();

                res.EmailDest = orderDetail.EmailDest;
                res.EuImprimo = orderDetail.EuImprimo;
                res.Mensagem = orderDetail.Mensagem;
                res.NomeDe = orderDetail.NomeDe;
                res.NomePara = orderDetail.NomePara;

                cartItem.DadosOferta = res;

                // Save it
                gr.SaveChanges();
                return true;
            }
            catch (Exception)
            {
                return false;
            }
        }

        public void RemoveFromCart(int id,bool RemoveAll)
        {
            //Get the cart
            var cartItem = gr.Cart.Include("Deal").Single(
                cart => (cart.IdSession == shoppingCartId || cart.ClienteId == IDCliente)
                && cart.Id == id);

            if (cartItem != null)
            {
                if (cartItem.Quantidade > 1 && !RemoveAll)
                {
                    cartItem.Quantidade--;
                    LastCartCount = cartItem.Quantidade;
                }
                else
                {
                    gr.Cart.DeleteObject(cartItem);
                    LastCartCount = 0;
                }
                gr.SaveChanges();
            }
        }

        public void EmptyCart()
        {
            var cartItems = gr.Cart
                .Where(cart => cart.IdSession == shoppingCartId || cart.ClienteId == IDCliente);

            foreach (var cartItem in cartItems)
            {
                gr.DeleteObject(cartItem);
            }

            gr.SaveChanges();
        }

        public List<Cart> GetCartItems()
        {
            var cartItems = (from cart in gr.Cart.Include("Deal")
                             where (cart.IdSession == shoppingCartId || cart.ClienteId == IDCliente)
                             select cart).ToList();
            return cartItems;
        }

        public int GetCount()
        {
            int? count = (from cartItems in gr.Cart
                          where (cartItems.IdSession == shoppingCartId || cartItems.ClienteId == IDCliente)
                          select (int?)cartItems.Quantidade).Sum();

            return count ?? 0;
        }

        public decimal GetTotal()
        {
            decimal? total =
                (from cartItems in gr.Cart
                 where (cartItems.IdSession == shoppingCartId || cartItems.ClienteId == IDCliente)
                 select (int?)cartItems.Quantidade * cartItems.Deal.PrecoDesconto)
                .Sum();

            return total ?? decimal.Zero;
        }

        public decimal GetTotalPontos()
        {
            decimal? total =
                (from cartItems in gr.Cart
                 where (cartItems.IdSession == shoppingCartId || cartItems.ClienteId == IDCliente)
                 select (int?)cartItems.Quantidade * cartItems.Deal.PrecoDesconto - cartItems.Pontos)
                .Sum();

            return total ?? decimal.Zero;
        }

        public decimal GetTotalByID(int id)
        {
            decimal? total =
                (from cartItems in gr.Cart
                 where (cartItems.Id == id && cartItems.ClienteId == IDCliente)
                 select (int?)cartItems.Quantidade * cartItems.Deal.PrecoDesconto)
                .Sum();

            return total ?? decimal.Zero;
        }

        public int CreateOrder(DAL.Order order)
        {
            var cartItems = GetCartItems().SingleOrDefault();

            //Iterate the items in the cart, adding Order Details for each
            //foreach (var cartItem in cartItems)
            //{
                var orderDetails = new OrderDetail
                {
                    DealId = cartItems.DealId,
                    OrderId = order.Id,
                    ValorUn = cartItems.Deal.PrecoDesconto,
                    Quantidade = cartItems.Quantidade,
                    Oferta = cartItems.Oferta,
                    DadosOferta = cartItems.DadosOferta,
                    Pontos = cartItems.Pontos,
                    Desconto = cartItems.Desconto
                };

                gr.OrderDetail.AddObject(orderDetails);
            //}
            
            //Save the order
            gr.SaveChanges();

            //Empty the shopping cart
            EmptyCart();

            //Return the OrderId as a confirmation number
            return order.Id;
        }

        // We're using HttpContextBase to allow access to cookies.
        public String GetCartId(HttpContextBase context)
        {
            if (context.Session[CartSessionKey] == null)
            {
                if (!string.IsNullOrWhiteSpace(context.User.Identity.Name))
                {
                    // User is logged in, associate the cart with there username
                    context.Session[CartSessionKey] = context.User.Identity.Name;
                }
                else
                {
                    // Generate a new random GUID using System.Guid Class
                    Guid tempCartId = Guid.NewGuid();

                    // Send tempCartId back to client as a cookie
                    context.Session[CartSessionKey] = tempCartId.ToString();
                }
            }
            return context.Session[CartSessionKey].ToString();
        }

        //public String GetCartId(HttpContextBase context)
        //{
        //    if (context.Request.Cookies[CartSessionKey] == null)
        //    {
        //        HttpCookie cookie;
                
        //        if (!string.IsNullOrWhiteSpace(context.User.Identity.Name))
        //        {
        //            // User is logged in, associate the cart with there username
        //            cookie = new HttpCookie(CartSessionKey, context.User.Identity.Name);
        //            context.Response.Cookies.Add(cookie);
        //        }
        //        else
        //        {
        //            // Generate a new random GUID using System.Guid Class
        //            Guid tempCartId = Guid.NewGuid();

        //            // Send tempCartId back to client as a cookie
        //            cookie = new HttpCookie(CartSessionKey, tempCartId.ToString());
        //            context.Response.Cookies.Add(cookie);
        //        }
        //        cookie.Expires = DateTime.Now.AddDays(5);
        //    }
        //    return context.Request.Cookies[CartSessionKey].Value.ToString();
        //}

        // When a user has logged in, migrate their shopping cart to
        // be associated with their username
        public void MigrateCart(string userName)
        {
            var shoppingCart = gr.Cart
                .Where(c => c.IdSession == shoppingCartId || c.ClienteId == IDCliente);

            foreach (Cart item in shoppingCart)
            {
                item.ClienteId = int.Parse(userName);
            }
            gr.SaveChanges();
        }
    }
}